package com.yhj.wchat.utils;


import com.yhj.wchat.entity.dto.MessageSendDto;
import com.yhj.wchat.entity.dto.TokenUserInfoDto;
import com.yhj.wchat.mj.MessageSend2TypeEnum;
import com.yhj.wchat.redis.RedisComponent;
import io.netty.channel.Channel;
import io.netty.channel.group.ChannelGroup;
import io.netty.channel.group.DefaultChannelGroup;
import io.netty.handler.codec.http.websocketx.TextWebSocketFrame;
import io.netty.util.AttributeKey;
import io.netty.util.concurrent.GlobalEventExecutor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;

import java.util.concurrent.ConcurrentHashMap;

@Component
@Slf4j
public class ChannelContextUtils {
    public static final ConcurrentHashMap<String, Channel> USER_CONTEXT_MAP = new ConcurrentHashMap<>();
    public static final  ConcurrentHashMap<String, ChannelGroup> MEETING_ROOM_CONTEXT_MAP = new ConcurrentHashMap<>();
    private final RedisComponent redisComponent;

    public ChannelContextUtils( RedisComponent redisComponent) {
        this.redisComponent = redisComponent;
    }
    public void addChannel(String userId, Channel channel){
        try {
            String channelId = channel.id().toString();
            AttributeKey attributeKey = null;
            if(!AttributeKey.exists(channelId)){
                attributeKey = AttributeKey.newInstance(channelId);
            }
            else {
                attributeKey = AttributeKey.valueOf(channelId);
            }
            channel.attr(attributeKey).set(userId);
            USER_CONTEXT_MAP.put(userId,channel);

            TokenUserInfoDto tokenUserInfoDto = redisComponent.getTokenUserInfoDtoByUserId(userId);

        }catch (Exception e){
            log.error("addChannel error",e);
        }
    }
    public void addMeetingRoom(String meetingId,String userId){
        try {
            Channel context = USER_CONTEXT_MAP.get(userId);
            if(context == null){
                return;
            }
            ChannelGroup group = MEETING_ROOM_CONTEXT_MAP.get(meetingId);
            if(group == null){
                group = new DefaultChannelGroup(GlobalEventExecutor.INSTANCE);
                MEETING_ROOM_CONTEXT_MAP.put(meetingId,group);
            }
            Channel channel = group.find(context.id());
            if (channel == null) {
                group.add(context);
            }

        }catch (Exception e){
            log.error("addMeetingRoom error",e);
        }
    }
    public void sendMessage(MessageSendDto messageSendDto){
        if (MessageSend2TypeEnum.USER.getType().equals(messageSendDto.getMessageSend2Type())) {
            sendMsg2User(messageSendDto);
        }else {
            sendMsg2Group(messageSendDto);
        }
    }
    private void sendMsg2User(MessageSendDto messageSendDto){
        if (messageSendDto.getReceiveUserId() == null) {
            return;
        }
        Channel channel = USER_CONTEXT_MAP.get(messageSendDto.getReceiveUserId());
        if (channel == null) {
            return;
        }
        channel.writeAndFlush(new TextWebSocketFrame(JsonUtils.convertObj2JsonWithLongToString(messageSendDto)));
    }
    private void sendMsg2Group(MessageSendDto messageSendDto){
    return;
    }

    private void removeContextGroup(String meetingId) {
        MEETING_ROOM_CONTEXT_MAP.remove(meetingId);
    }

    private void removeContextFromGroup(String exitUserId, String meetingId) {
        Channel context = USER_CONTEXT_MAP.get(exitUserId);
        if (context == null) {
            return;
        }
        ChannelGroup group = MEETING_ROOM_CONTEXT_MAP.get(meetingId);
        if (group == null) {

            group.remove(context);
        }


    }

    public void closeContext(String userId){
        if (StringTools.isEmpty(userId)) {
            return;
        }
        Channel channel = USER_CONTEXT_MAP.get(userId);
        USER_CONTEXT_MAP.remove(userId);
        if (channel != null) {
            channel.close();
        }
    }
}
